/**
 * @param {Object} args
 * @returns {string}
 *
 classNames('foo', 'bar'); // => 'foo bar'
 classNames('foo', { bar: true }); // => 'foo bar'
 classNames({ 'foo-bar': true }); // => 'foo-bar'
 classNames({ 'foo-bar': false }); // => ''
 classNames({ foo: true }, { bar: true }); // => 'foo bar'
 classNames({ foo: true, bar: true }); // => 'foo bar'

 // lots of arguments of various types
 classNames('foo', { bar: true, duck: false }, 'baz', { quux: true }); // => 'foo bar baz quux'

 // other falsy values are just ignored
 classNames(null, false, 'bar', undefined, 0, 1, { baz: null }, ''); // => 'bar 1'

 var arr = ['b', { c: true, d: false }];
 classNames('a', arr); // => 'a b c'

 let buttonType = 'primary';
 classNames({ [`btn-${buttonType}`]: true });
 */
export function clsx(...args: any[]): string {
	const classes: string[] = []
	for (let i = 0; i < args.length; i++) {
		const arg = args[i]
		if (!arg) continue

		const argType = typeof arg

		if (argType === 'string' || argType === 'number') {
			classes.push(arg)
		} else if (Array.isArray(arg) && arg.length) {
			const inner = clsx.apply(null, arg)
			if (inner) classes.push(inner)
		} else if (argType === 'object') {
			for (const key in arg) {
				if (Object.hasOwn(arg, key) && arg[key]) {
					classes.push(key)
				}
			}
		}
	}

	return classes.join(' ')
}

